/*
 *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that the following conditions are met:
 *
 *  Redistributions of source code must retain the above copyright notice,
 *  this list of conditions and the following disclaimer.
 *  Redistributions in binary form must reproduce the above copyright
 *  notice, this list of conditions and the following disclaimer in the
 *  documentation and/or other materials provided with the distribution.
 *  Neither the name of the dreamlu.net developer nor the names of its
 *  contributors may be used to endorse or promote products derived from
 *  this software without specific prior written permission.
 *  Author: Chill 庄骞 (smallchill@163.com)
 */
package org.springblade.mach.service.impl;


import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import io.jsonwebtoken.lang.Collections;
import io.minio.MinioClient;
import io.minio.errors.*;
import liquibase.pro.packaged.L;
import lombok.AllArgsConstructor;
import lombok.SneakyThrows;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.springblade.core.log.exception.ServiceException;
import org.springblade.core.oss.model.BladeFile;
import org.springblade.core.secure.utils.AuthUtil;
import org.springblade.core.tool.api.R;
import org.springblade.core.tool.utils.FileUtil;
import org.springblade.core.tool.utils.Func;
import org.springblade.core.tool.utils.StringPool;
import org.springblade.core.tool.utils.StringUtil;
import org.springblade.mach.entity.*;
import org.springblade.mach.service.*;
import org.springblade.mach.utils.ExcelUtils;
import org.springblade.mach.utils.MachUtils;
import org.springblade.mach.vo.DrawingUploadVO;
import org.springblade.mach.mapper.DrawingUploadMapper;
import org.springblade.core.mp.base.BaseServiceImpl;
import org.springblade.mach.vo.SignDrawingUploadVO;
import org.springblade.modules.resource.builder.oss.OssBuilder;
import org.springblade.modules.resource.builder.oss.UploadFileBuilder;
import org.springblade.modules.resource.entity.Attach;
import org.springblade.modules.resource.entity.Oss;
import org.springblade.modules.resource.service.IAttachService;
import org.springblade.modules.resource.vo.AttachVO;
import org.springframework.stereotype.Service;
import com.baomidou.mybatisplus.core.metadata.IPage;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;
import org.xmlpull.v1.XmlPullParserException;

import java.io.IOException;
import java.io.InputStream;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.util.*;
import java.util.stream.Collectors;

/**
 * 服务实现类
 *
 * @author LY
 * @since 2021-03-09
 */
@Service
@AllArgsConstructor
public class DrawingUploadServiceImpl extends BaseServiceImpl<DrawingUploadMapper, DrawingUpload> implements IDrawingUploadService {
	private IAttachService attachService;

	private IDrawingUploadDetailService drawingUploadDetailService;

	// excel操作类
	private ExcelUtils excelUtils;
	private MachUtils machUtils;
	// 图纸节点信息
	private IDrawingInfoNodeService drawingInfoNodeService;
	// 对象存储构建类
	private OssBuilder ossBuilder;
	// 图纸附件表业务类
	private final IDrawingAttachApprovalService drawingAttachApprovalService;
	// 项目管理实体类
	private final IProjectManaService projectManaService;
	// 图纸附件
	private IDrawingInfoAttachService drawingInfoAttachService;

	private IStandardPartsService standardPartsService;

	private IPurchasedPartsService purchasedPartsService;
	private IDrawingInfoService drawingInfoService;
	private IDrawingNumberApplicationDetailService drawingNumberApplicationDetailService;

	@Override
	public IPage<DrawingUploadVO> selectDrawingAttachPage(IPage<DrawingUploadVO> page, DrawingUploadVO drawingAttach) {
		return page.setRecords(baseMapper.selectDrawingAttachPage(page, drawingAttach));
	}

	@Override
	@Transactional(rollbackFor = Exception.class)
	public boolean updateDrawingStatus(Long drawingId, Integer statusCode) {
		if (drawingId == null) {
			throw new ServiceException("图纸主键不能为空!");
		}
		DrawingUpload drawingUpload = new DrawingUpload();
		drawingUpload.setId(drawingId);
		drawingUpload.setStatus(statusCode);
		int result = baseMapper.updateById(drawingUpload);
		if (result > 0) {
			return true;
		} else {
			return false;
		}
	}

	@Override
	public DrawingUpload getDrawingDetail(String wordOrderNo, String drawingNumber) {
		if (StringUtil.isEmpty(wordOrderNo)) {
			throw new ServiceException("工单号不能为空!");
		}
		if (StringUtil.isEmpty(drawingNumber)) {
			throw new ServiceException("设备编号不能为空!");
		}
		return baseMapper.getDrawingDetail(wordOrderNo, drawingNumber);
	}

	@Override
	@Transactional(rollbackFor = Exception.class)
	public R<Map<String, Object>> saveUploadAttach(MultipartFile[] file,
												   MultipartFile[] threeFile,
												   MultipartFile[] imgFile,
												   DrawingUpload drawingUpload,
												   FileTyeList fileTyeList,
												   FileThreeTypeList fileThreeTypeList,
												   FileImgTypeList fileImgTypeList) {
		List<DrawingUploadDetail> detailList = new ArrayList<>();
		Map<String, Object> pageMap = new HashMap<>();
		drawingUpload.setStatus(DrawingUpload.STATUS_PENDING);
		boolean saveDrawingUpload;
		if (null != drawingUpload.getId()) {
			saveDrawingUpload = updateById(drawingUpload);
		} else {
			saveDrawingUpload = save(drawingUpload);
		}
		List<AttachVO> drawingByUploadId = attachService.getDrawingByUploadId(drawingUpload.getId());
		if (fileTyeList != null) {
			// 页面传递过来的数据
			List<FileType> excelFileList = fileTyeList.getFileTypeList();
			removeAttach(excelFileList, drawingUpload, drawingByUploadId);
		}
		List<AttachVO> threeAttachDB = attachService.getThreeDrawingByUploadId(drawingUpload.getId());
		if (fileThreeTypeList != null) {
			// 页面传递过来的数据
			List<FileType> threeFileList = fileThreeTypeList.getThreeFileTypeList();
			removeAttach(threeFileList, drawingUpload, threeAttachDB);
		}
		List<AttachVO> imgAttachDB = attachService.getImgListByUploadId(drawingUpload.getId());
		if (fileImgTypeList != null) {
			// 页面传递过来的数据
			List<FileType> imgFileList = fileImgTypeList.getFileImgTypeList();
			removeAttach(imgFileList, drawingUpload, imgAttachDB);
		}
		// 上传的附件excel
		if (file.length > 0) {
			saveAttached(file, detailList, drawingUpload, "平面");
		}
		// 三维图纸附件
		if (threeFile.length > 0) {
			saveAttached(threeFile, detailList, drawingUpload, "三维");
		}
		// 图纸截图信息
		if (imgFile.length > 0) {
			saveAttached(imgFile, detailList, drawingUpload, "图片");
		}
		Boolean saveDetail = false;
		if (Collections.isEmpty(detailList)) {
			saveDetail = true;
		} else {
			saveDetail = drawingUploadDetailService.saveBatch(detailList);
		}
		if (saveDetail && saveDrawingUpload) {
			pageMap.put("right", "上传成功");
		} else {
			pageMap.put("error", "上传失败");
		}
		return R.data(pageMap);
	}

	/**
	 * 根据前端提交的删除图纸附件
	 *
	 * @param ids 列表id
	 * @return
	 */
	@Override
	public R removeAttach(String ids) {
		// step1:删除记录的列表id
		List<Long> idList = Func.toLongList(ids);
		// step2:逻辑删除upload、中间表、attach表中的记录
		List<DrawingUploadDetail> detailList = drawingUploadDetailService.
			list(new QueryWrapper<DrawingUploadDetail>().in("upload_id", idList));
		List<Long> detailIdList = new ArrayList<>();
		List<Long> attachIdList = new ArrayList<>();
		detailList.stream().forEach(detail -> {
			detailIdList.add(detail.getId());
			attachIdList.add(detail.getAttachId());
		});
		// 删除服务器上oss附件的信息
		if (!Collections.isEmpty(attachIdList)) {
			List<Attach> attachList = attachService.listByIds(attachIdList);
			if (!Collections.isEmpty(attachList)) {
				for (int i = 0; i < attachList.size(); i++) {
					ossBuilder.template().removeFile("machtech", attachList.get(i).getName());
				}
			}
		}

		boolean deleteDetail = drawingUploadDetailService.deleteLogic(detailIdList);
		boolean deleteAttach = attachService.deleteLogic(attachIdList);
		boolean deleteUpload = deleteLogic(idList);

		return R.status(deleteDetail && deleteAttach && deleteUpload);
	}

	/**
	 * 判断文件是否是excel，且忽略大小写（原先写法不忽略大小写，如文件拓展名大写就无法走判断）
	 *
	 * @param fileName
	 * @return
	 */
	@Override
	public Boolean checkExcel(String fileName) {
		return StringUtil.endsWithIgnoreCase(fileName, "xls") || StringUtil.endsWithIgnoreCase(fileName, "xlsx");
	}

	/**
	 * @param excelFileList
	 * @param drawingUpload
	 * @param attachListDB
	 * @return void
	 * 删除修改图纸时删除掉的文件
	 * @Author zhp
	 * @Description //TODO
	 * @Date 17:33 2022/1/17
	 */
	@Transactional(rollbackFor = Exception.class)
	public void removeAttach(List<FileType> excelFileList, DrawingUpload drawingUpload, List<AttachVO> attachListDB) {
		if (CollectionUtils.isNotEmpty(attachListDB)) {
			//前端传入的未新增前的file
			List<String> nowFileUrl = excelFileList != null ? excelFileList.stream().map(FileType::getUrl).collect(Collectors.toList()) : Lists.newArrayList();
			//数据库中的file
			List<String> dbFileUrl = attachListDB.stream().map(Attach::getLink).collect(Collectors.toList());
			if (dbFileUrl.removeAll(nowFileUrl) || nowFileUrl.size() == 0) {
				if (CollectionUtils.isNotEmpty(dbFileUrl)) {
					for (int i = 0; i < dbFileUrl.size(); i++) {
						Attach attachVO = attachService.getOne(new QueryWrapper<Attach>().lambda().eq(Attach::getLink, dbFileUrl.get(i)));
						if (attachVO != null) {
							List<DrawingUploadDetail> detailList = drawingUploadDetailService.list(
								new QueryWrapper<DrawingUploadDetail>().
									eq("upload_id", drawingUpload.getId()).
									eq("attach_id", attachVO.getId()));
							List<Long> detailIds = detailList.stream().map(DrawingUploadDetail::getId).collect(Collectors.toList());
							// 删除中间表得记录 upload_detail
							drawingUploadDetailService.deleteLogic(detailIds);
							// 删除attch表中得记录
							attachService.removeById(attachVO.getId());
							List<Long> attachList = new ArrayList<>();
							attachList.add(attachVO.getId());
							attachService.deleteLogic(attachList);
							// 删除服务oss上的数据
							ossBuilder.template().removeFile("machtech", attachVO.getName());
						}
					}
				}
			}
		}
	}

	/**
	 * 构建附件表
	 *
	 * @param fileName  文件名
	 * @param fileSize  文件大小
	 * @param bladeFile 对象存储文件
	 * @return attachId
	 */
	public Attach buildAttach(String fileName, Long fileSize, BladeFile bladeFile) {
		String fileExtension = FileUtil.getFileExtension(fileName);
		Attach attach = new Attach();
		attach.setDomain(bladeFile.getDomain());
		attach.setLink(bladeFile.getLink());
		attach.setName(bladeFile.getName());
		attach.setOriginalName(fileName);
		attach.setAttachSize(fileSize);
		attach.setExtension(fileExtension);
		return attach;
	}

	/**
	 * 保存附件
	 *
	 * @param files         附件
	 * @param detailList    设备以及图纸的对应信息
	 * @param drawingUpload
	 * @param type          附件类型
	 */
	public void saveAttached(MultipartFile[] files,
							 List<DrawingUploadDetail> detailList,
							 DrawingUpload drawingUpload,
							 String type) {
		for (int i = 0; i < files.length; i++) {
			MultipartFile indexFile = files[i];
			if (!indexFile.isEmpty()) {
				String fileName = indexFile.getOriginalFilename();
				BladeFile bladeFile = UploadFileBuilder.handlePutFile(fileName, indexFile, ossBuilder);
				Attach attach = buildAttach(fileName, indexFile.getSize(), bladeFile);
				attach.setType(type);
				attachService.save(attach);
				// 附件详情表
				DrawingUploadDetail detail = new DrawingUploadDetail();
				detail.setAttachId(attach.getId());
				detail.setUploadId(drawingUpload.getId());
				detailList.add(detail);
			}
		}
	}

	/**
	 * 上传替换签名后的图纸信息
	 * @param signDrawingUploadVO
	 * @return
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public R<Map<String, Object>> saveSignAttach(SignDrawingUploadVO signDrawingUploadVO) {
		Map<String, Object> pageMap = new HashMap<>();
		Long uploadId = signDrawingUploadVO.getDrawingUploadId();
		//检查数据库中是否有附件
		List<AttachVO> attachList = attachService.findDrawingListByUploadId(uploadId, signDrawingUploadVO.getTaskDefinitionKey());
		// 删除附件及关联数据信息
		if (attachList.size() > 0){
			pageMap.put("msg",handleDrawingAttach(uploadId, signDrawingUploadVO.getTaskDefinitionKey()));
		}
		// 新增平面图纸
		MultipartFile[] planeFiles = signDrawingUploadVO.getPlaneFile();
		boolean savePlan = saveReplace(planeFiles,"平面", uploadId);
		// 三维图纸上传
		MultipartFile[] dimensionalFiles = signDrawingUploadVO.getDimensionalFile();
		boolean saveTri;
		if (dimensionalFiles != null && dimensionalFiles.length > 0){
			saveTri = saveReplace(dimensionalFiles,"三维", uploadId);
		} else {
			saveTri = true;
		}
		if (savePlan && saveTri) {
			pageMap.put("right", "上传成功");
		} else {
			pageMap.put("error", "上传失败");
		}
		return R.data(pageMap);
	}

	/**
	 * 替换图纸上传功能封装
	 * @param files
	 * @param type
	 * @param uploadId
	 * @return
	 */
	public Boolean saveReplace(MultipartFile[] files,String type, Long uploadId){
		Boolean result = false;
		Integer saveAttach = 0;
		Integer saveDetail = 0;
		if (files != null && files.length > 0) {
			for (MultipartFile file : files) {
				// 附件
				String fileName = file.getOriginalFilename();
				BladeFile bladeFile = UploadFileBuilder.handlePutFile(fileName, file, ossBuilder);
				Attach attach = buildAttach(fileName, file.getSize(), bladeFile);
				attach.setType(type);
				if (attachService.save(attach)){
					saveAttach++;
				}
				// 图纸与附件关联表
				DrawingUploadDetail detail = new DrawingUploadDetail();
				detail.setAttachId(attach.getId());
				detail.setUploadId(uploadId);
				if (drawingUploadDetailService.save(detail)){
					saveDetail++;
				}
			}
			if (saveAttach.equals(saveDetail)){
				result = true;
			}
		}
		return result;
	}

	/**
	 * 删除附件及关联信息
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public R handleDrawingAttach(Long uploadId, String taskDefinitionKey) {
		Boolean result = false;
		List<AttachVO> attachList = attachService.findDrawingListByUploadId(uploadId, taskDefinitionKey);
		List<Long> attachIdList = attachList.stream().map(AttachVO::getId).collect(Collectors.toList());
		if (!Collections.isEmpty(attachList)) {
			// 删除MinIO服务器上附件
			attachList.stream().forEach(attachVO -> ossBuilder.template().removeFile(attachVO.getName()));
			// 物理删除附件列表
			//List<Long> attachIdList = drawingUploadDetailService.findAttachIdList(uploadId);
			attachService.deleteAttachByIds(attachIdList);
			// 物理删除图纸与附件关联信息
			//drawingUploadDetailService.deleteDrawingUploadDetail(uploadId);
			drawingUploadDetailService.removeByAttachtIds(attachIdList);
			// 物理删除图纸附件审批信息
			result = drawingAttachApprovalService.logicDelApproval(uploadId, taskDefinitionKey);

		}
		if (result) {
			return R.data(true);
		} else {
			return R.fail("删除失败");
		}
	}

	/**
	 * @param id
	 * @return void
	 * 拆分bom
	 * @Author zhp
	 * @Description //TODO
	 * @Date 10:32 2021/11/29
	 */
	@Override
	@Transactional(rollbackFor = Exception.class)
	public void getDrawingBom(Long id) throws Exception {
		// 获取uploadId所有的附件信息
		List<AttachVO> allAttachList = attachService.findAllUploadId(id);

		// List元素按照附件名称进行分类
		Map<String, List<AttachVO>> collect = allAttachList.stream().collect(Collectors.groupingBy(AttachVO::getOriginalName));

		// step1:先整合excel中对应的bom信息
		List<AttachVO> allExcel = attachService.getBomExcelByUploadId(id);    // 这个是所有的excel的附件信息
		List<AttachVO> allPic = attachService.getImgListByUploadId(id);
		Map<String, Object> map = Maps.newHashMap();
		for (AttachVO attachVO : allExcel) {
			map.put(attachVO.getOriginalName().split("-")[0].trim(), attachVO.getName());
		}
		for (int i = 0; i < allExcel.size(); i++) {
			// 设备编号
			String drawingNumber = allExcel.get(i).getOriginalName().substring(0, 13);
//			if (!drawingNumber.substring(5,7).equals("00")) {
			if (drawingNumber.contains("MH")) {
				String fileNameServer = allExcel.get(i).getName();
				// 父节点信息
				DrawingInfo parent = drawingInfoService.getDrawingInfoByDrawingNumber(drawingNumber);
				if (parent == null) {
					parent = new DrawingInfo();
					parent.setDrawingNumber(drawingNumber);
					if (drawingNumber.contains("MH")) {
						// 图纸类型
						parent.setDrawingType(drawingNumber.substring(5, 7));
					}
					drawingInfoService.save(parent);
				}
				//截图绑定01图号的parentId
				String treeTopNode = parent.getDrawingType();
				if ("01".equals(treeTopNode) && CollectionUtils.isNotEmpty(allPic)){
					Long parentId = parent.getId();
					allPic.forEach(attachVO -> {
						DrawingInfoAttach infoAttach = new DrawingInfoAttach();
						infoAttach.setAttachId(attachVO.getId());
						infoAttach.setDrawingInfoId(parentId);
						infoAttach.setVersion("1");
						drawingInfoAttachService.save(infoAttach);
					});
				}
				// 如果节点信息存在 不需要重复传入数据
				DrawingInfoNode parentNode = drawingInfoNodeService.getOne(new QueryWrapper<DrawingInfoNode>().
					eq("parent_id", 0).
					eq("child_id", parent.getId()));
				if (parentNode == null) {
					parentNode = new DrawingInfoNode();
					// 当前父节点信息
					parentNode.setParentId(0L);
					parentNode.setChildId(parent.getId());
					parentNode.setNum("1");
					drawingInfoNodeService.save(parentNode);
				}

				// 父节点对应的attach_id 判断记录是否存在
				if (drawingNumber.contains("MH")) {
					// 模糊匹配Map中的值
					for (Map.Entry entity : collect.entrySet()) {
						// 表示记录存在 如果没有找到记录，返回-1
						if (entity.getKey().toString().length() > 13 && ((String) entity.getKey()).substring(0, 13).indexOf(drawingNumber) > -1) {
							List<AttachVO> attachList = collect.get(entity.getKey());
							for (int j = 0; j < attachList.size(); j++) {
								DrawingInfoAttach infoAttach = drawingInfoAttachService.getOne(new QueryWrapper<DrawingInfoAttach>().
									eq("drawing_info_id", parent.getId()).
									eq("attach_id", attachList.get(j).getId()).
									eq("version", "1"));
								if (infoAttach == null) {
									infoAttach = new DrawingInfoAttach();
									// 父节点对应的attach_id
									infoAttach.setAttachId(attachList.get(j).getId());
									infoAttach.setDrawingInfoId(parent.getId());
									infoAttach.setVersion("1");
									drawingInfoAttachService.save(infoAttach);
								}
							}
						}
					}
				}



				// 读取内容
				List<ReadExcelEntity> excelEntityList = excelUtils.getExcelEntityList("000000-machtech", fileNameServer);

				for (int j = 0; j < excelEntityList.size(); j++) {
					// ##########step2处理info表中的记录
					// 读取的bom信息
					ReadExcelEntity readExcelEntity = excelEntityList.get(j);

					// BOM的info明细
					DrawingInfo drawingInfoDB = null;
					if (readExcelEntity.getDrawingNumber().contains("MH")) {
						drawingInfoDB = drawingInfoService.getOne(new QueryWrapper<DrawingInfo>().
							eq("drawing_number", readExcelEntity.getDrawingNumber()));
					} else {
						// 非MH的BOM明细
						drawingInfoDB = drawingInfoService.getOne(new QueryWrapper<DrawingInfo>().
							eq("drawing_number", readExcelEntity.getDrawingNumber()).
							eq("drawing_name", readExcelEntity.getDrawingName()).
							eq("remark", readExcelEntity.getRemark()));
					}

					// 处理info表中bom信息  更新操作
					if (drawingInfoDB != null) {
//						图纸信息上传完不允许更新
						if (StringUtil.isBlank(drawingInfoDB.getDrawingName())) {
							readExcelEntity = machUtils.getBomOwnAttribute(readExcelEntity, map);
							drawingInfoDB.setDrawingNumber(readExcelEntity.getDrawingNumber());
							drawingInfoDB.setDrawingName(readExcelEntity.getDrawingName());
							drawingInfoDB.setMaterial(readExcelEntity.getMaterial());
							drawingInfoDB.setSingleWeight(readExcelEntity.getSingleWeight());
							drawingInfoDB.setDrawingProperty(readExcelEntity.getDrawingProperty());
							drawingInfoDB.setRemark(readExcelEntity.getRemark());
							//属性值只保存当前excel里面的,本级中体现当前图号的属性值
							if (drawingNumber.equals(readExcelEntity.getDrawingNumber())) {
								drawingInfoDB.setCharacOne(readExcelEntity.getCharacOne());
								drawingInfoDB.setCharacTwo(readExcelEntity.getCharacTwo());
								drawingInfoDB.setCharacThree(readExcelEntity.getCharacThree());
							}
							if (readExcelEntity.getDrawingNumber().contains("MH")) {
								drawingInfoDB.setDrawingType(readExcelEntity.getDrawingNumber().substring(5, 7));
								// 保存attach_id表中的记录
							}
							drawingInfoService.updateById(drawingInfoDB);
						}

					} else {
						if (readExcelEntity.getDrawingNumber().contains("MH")) {
							readExcelEntity.setDrawingType(readExcelEntity.getDrawingNumber().substring(5, 7));
							//此处需要从自身BOM中获取属性等信息
							readExcelEntity = machUtils.getBomOwnAttribute(readExcelEntity, map);
							//修改图号状态
							final DrawingNumberApplicationDetail drawingNumberApplicationDetail = drawingNumberApplicationDetailService.
								getOne(new QueryWrapper<DrawingNumberApplicationDetail>().eq("number", readExcelEntity.getDrawingNumber()));
							drawingNumberApplicationDetail.setStatus(DrawingNumberApplicationDetail.STATUS_ARCHIVED);
							drawingNumberApplicationDetailService.updateById(drawingNumberApplicationDetail);
						}
						boolean save = drawingInfoService.save(readExcelEntity);
						if (save) {
							if (readExcelEntity.getDrawingNumber().contains("MH")) {
								// 图纸编号  节点信息展示，info-attach
								String number = readExcelEntity.getDrawingNumber();
								for (Map.Entry entity : collect.entrySet()) {
									if (entity.getKey().toString().length() > 13 && ((String) entity.getKey()).substring(0, 13).indexOf(number) > -1) {
										List<AttachVO> attachList = collect.get(entity.getKey());
										for (int k = 0; k < attachList.size(); k++) {
											DrawingInfoAttach infoAttach = drawingInfoAttachService.getOne(new QueryWrapper<DrawingInfoAttach>().
												eq("drawing_info_id", readExcelEntity.getId()).
												eq("attach_id", attachList.get(k).getId()).
												eq("version", "1"));
											if (infoAttach == null) {
												infoAttach = new DrawingInfoAttach();
												// 父节点对应的attach_id
												infoAttach.setAttachId(attachList.get(k).getId());
												infoAttach.setDrawingInfoId(readExcelEntity.getId());
												infoAttach.setVersion("1");
												drawingInfoAttachService.save(infoAttach);
											}
										}
									}
								}
							}
						}
					}

					// 数据库中的记录,刘云原始代码
					/*DrawingInfo info = drawingInfoService.getOne(new QueryWrapper<DrawingInfo>().
						eq("drawing_number",readExcelEntity.getDrawingNumber()).
						eq("drawing_name",readExcelEntity.getDrawingName()));*/

					// 数据库中的记录,zhp修改
					DrawingInfo info = drawingInfoService.list(new QueryWrapper<DrawingInfo>().
						eq("drawing_number", readExcelEntity.getDrawingNumber()).
						eq("drawing_name", readExcelEntity.getDrawingName())).get(0);

					// node表中节点信息
					if (!parent.getId().equals(info.getId())) {
						DrawingInfoNode node = drawingInfoNodeService.getOne(new QueryWrapper<DrawingInfoNode>().
							eq("parent_id", parent.getId()).
							eq("child_id", info.getId()));
						if (node == null) {
							node = new DrawingInfoNode();
							node.setParentId(parent.getId());
							node.setChildId(info.getId());
							node.setNum(readExcelEntity.getBomNum());
							drawingInfoNodeService.save(node);
						}
					}

					//###########step3:处理物料标准库表中的记录(现统计为属性值 应该为备注信息)
					if (StringUtil.equals(readExcelEntity.getDrawingProperty(), "标准件")) {
						// 查询数据库中是否有记录
						StandardParts standardPartsDB = standardPartsService.getOne(new QueryWrapper<StandardParts>().
							eq("code", readExcelEntity.getDrawingNumber()).
							eq("name", readExcelEntity.getDrawingName()));
						if (standardPartsDB != null) {
							standardPartsDB.setCode(readExcelEntity.getDrawingNumber());
							standardPartsDB.setName(readExcelEntity.getDrawingName());
							standardPartsDB.setMaterial(readExcelEntity.getMaterial());
							standardPartsDB.setSingleWeight(readExcelEntity.getSingleWeight());
							standardPartsService.updateById(standardPartsDB);
						} else {
							// 无记录时，进行新增记录
							StandardParts standardParts = new StandardParts();
							standardParts.setCode(readExcelEntity.getDrawingNumber());
							standardParts.setName(readExcelEntity.getDrawingName());
							standardParts.setMaterial(readExcelEntity.getMaterial());
							standardParts.setSingleWeight(readExcelEntity.getSingleWeight());
							standardPartsService.save(standardParts);
						}
					}

					//###########step4:处理采购件表中的记录(现统计为属性值 应该为备注信息)
					if (StringUtil.equals(readExcelEntity.getDrawingProperty(), "采购件")) {
						// 查询数据库中是否有记录
						PurchasedParts purchasedPartsDB = purchasedPartsService.getOne(new QueryWrapper<PurchasedParts>().
							eq("code", readExcelEntity.getDrawingNumber()).
							eq("name", readExcelEntity.getDrawingName()));
						if (purchasedPartsDB != null) {
							purchasedPartsDB.setCode(readExcelEntity.getDrawingNumber());
							purchasedPartsDB.setName(readExcelEntity.getDrawingName());
							purchasedPartsDB.setMaterial(readExcelEntity.getMaterial());
							purchasedPartsDB.setSingleWeight(readExcelEntity.getSingleWeight());
							purchasedPartsService.updateById(purchasedPartsDB);
						} else {
							// 无记录时，进行新增记录
							PurchasedParts purchasedParts = new PurchasedParts();
							purchasedParts.setCode(readExcelEntity.getDrawingNumber());
							purchasedParts.setName(readExcelEntity.getDrawingName());
							purchasedParts.setMaterial(readExcelEntity.getMaterial());
							purchasedParts.setSingleWeight(readExcelEntity.getSingleWeight());
							purchasedPartsService.save(purchasedParts);
						}
					}
				}
			}
		}

		// 零件图对应的节点信息
		for (int i = 0; i < allExcel.size(); i++) {
			String drawingNumber = allExcel.get(i).getOriginalName().substring(0, 13);
			if (drawingNumber.substring(5, 7).equals("00")) {
				if (drawingNumber.contains("MH")) {
					DrawingInfo drawingInfo = drawingInfoService.getDrawingInfoByDrawingNumber(drawingNumber);
					if (drawingInfo != null) {
						// 模糊匹配Map中的值
						for (Map.Entry entity : collect.entrySet()) {
							// 表示记录存在 如果没有找到记录，返回-1
							if (entity.getKey().toString().length() > 13 && ((String) entity.getKey()).substring(0, 13).indexOf(drawingNumber) > -1) {
								List<AttachVO> attachList = collect.get(entity.getKey());
								for (int j = 0; j < attachList.size(); j++) {
									DrawingInfoAttach infoAttach = drawingInfoAttachService.getOne(new QueryWrapper<DrawingInfoAttach>().
										eq("drawing_info_id", drawingInfo.getId()).
										eq("attach_id", attachList.get(j).getId()).
										eq("version", "1"));
									if (infoAttach == null) {
										infoAttach = new DrawingInfoAttach();
										// 父节点对应的attach_id
										infoAttach.setAttachId(attachList.get(j).getId());
										infoAttach.setDrawingInfoId(drawingInfo.getId());
										infoAttach.setVersion("1");
										drawingInfoAttachService.save(infoAttach);
									}
								}
							}
						}
					}
				}
			}
		}
	}

	/**
	 * @param drawingUpload
	 * @return java.util.List<org.springblade.mach.entity.DrawingUpload>
	 * 根据上传图纸图号获取所有Excel中的图号
	 * @Author zhp
	 * @Description //TODO
	 * @Date 17:51 2022/1/20
	 */
	@Override
	public List<DrawingUpload> getDrawingExcelLinkName(DrawingUpload drawingUpload) {
		return baseMapper.getDrawingExcelLinkName(drawingUpload);
	}

	/**
	 * @Author zhp
	 * @Description //TODO
	 * @Date 18:27 2022/1/20
	 * @param drawingUploadId
	 * @param status
	 * @return void
	 * 修改图纸上传与图号状态
	*/
	@Override
	public Boolean updateDrawingUploadStatus(Long drawingUploadId, int status) throws Exception {
		//修改图纸上传状态为待审批
		final DrawingUpload drawingUpload = getById(drawingUploadId);
		final List<DrawingUpload> drawingExcelLinkName = getDrawingExcelLinkName(drawingUpload);
		Oss oss = ossBuilder.getOss(AuthUtil.getTenantId(), StringPool.EMPTY);
		MinioClient minioClient = new MinioClient(oss.getEndpoint(), oss.getAccessKey(), oss.getSecretKey());
		drawingExcelLinkName.forEach(e -> {
			InputStream is = null;
			try {
				is = minioClient.getObject("000000-machtech", e.getMaterial());
			} catch (Exception ex) {
				ex.printStackTrace();
			}
			Workbook wb = ExcelUtils.getServerWb(e.getMaterial(), is);
			final List<String> drawingNumberByExcel = machUtils.getDrawingNumberByExcel(wb);
			drawingNumberByExcel.forEach(d -> {
				final DrawingNumberApplicationDetail detailServiceOne = drawingNumberApplicationDetailService.getOne(
					new QueryWrapper<DrawingNumberApplicationDetail>().eq("number", d));
				if (detailServiceOne.getStatus() != DrawingNumberApplicationDetail.STATUS_ARCHIVED) {
					if (status == DrawingUpload.STATUS_APPROVAL) {
						detailServiceOne.setStatus(DrawingNumberApplicationDetail.STATUS_REVIEW);
					}else {
						detailServiceOne.setStatus(DrawingNumberApplicationDetail.STATUS_ARCHIVED);
					}
					drawingNumberApplicationDetailService.updateById(detailServiceOne);
				}
			});
		});
		Boolean b;
		if (status == DrawingUpload.STATUS_APPROVAL) {
			b = updateDrawingStatus(drawingUploadId, DrawingUpload.STATUS_APPROVAL);
		}else {
			b = updateDrawingStatus(drawingUploadId, DrawingUpload.STATUS_ARCHIVE);
		}
		return b;
	}

	/*
		1.先校验传来的xls里面有多少MH图号，
		2.然后校验MH图号中数据库里是否有存在的图纸
		3.如果存在可以不上传，如果不存在，则校验是否上传图纸了
	 */
	//**********************废弃***********************
	@Override
	public List<String> checkBom(MultipartFile[] files) {
		// 01+以上代码集合
		List<String> oneMoreCode = new ArrayList<>();
		// 上传文件中截取名称的集合
		List<String> fileCodeNameList = new ArrayList<>();
		// 返回的错误信息
		List<String> checkBomList = new ArrayList<>();
		for (int i = 0; i < files.length; i++) {
			MultipartFile indexFile = files[i];
			if (!indexFile.isEmpty()) {
				String fileName = indexFile.getOriginalFilename();
				if (checkExcel(fileName)) {
					// step1:先收集文件excel中，01+以上的代号.
					List<String> indexFileCode = readOneMoreExcelCode(indexFile);
					if (indexFileCode.size() > 0) {
						oneMoreCode.addAll(indexFileCode);
					}
					// step2:先收集文件excel文件中，包含的代号信息
					String fileCodeName = indexFile.getOriginalFilename().trim().substring(0, 13);
					fileCodeNameList.add(fileCodeName);
				}
			}
		}
		// 上传的附件中缺少相应的信息 或者是数据库中 没有该代号的附件信息
		for (int i = 0; i < oneMoreCode.size(); i++) {
			if (!fileCodeNameList.contains(oneMoreCode.get(i).trim())) {
				if (drawingInfoService.getDrawingInfoByDrawingNumber(oneMoreCode.get(i)) == null) {
					checkBomList.add("代号为" + oneMoreCode.get(i) + "的设备缺少相应的BOM信息");
				}
			}
			continue;
		}
		return checkBomList;
	}
	//**********************废弃***********************

	// 读取excel文件中01+以上的设备代号
	public List<String> readOneMoreExcelCode(MultipartFile file) {
		Workbook wb = ExcelUtils.getWb(file);
		Sheet sheetAt = wb.getSheetAt(0);
		List<String> readOneMoreNumberList = new ArrayList<>();
		for (int i = 1; i <= sheetAt.getLastRowNum(); i++) {
			Row row = sheetAt.getRow(i);//获取每一行的数据
			String drawingNumberFiles = String.valueOf(row.getCell(1).getStringCellValue());
			boolean contains = drawingNumberFiles.contains("MH");
			if (contains) {
				String code = drawingNumberFiles.substring(5, 7);
				if (Integer.valueOf(code) > 0) {
					readOneMoreNumberList.add(drawingNumberFiles);
				}
			}
		}
		return readOneMoreNumberList;
	}

	@Override
	public List<String> verifyBom(MultipartFile[] files){
		/*
		1.先校验传来的xls里面有多少MH图号，
		2.然后校验MH图号中数据库里是否有存在的图纸
		3.如果存在可以不上传，如果不存在，则校验是否上传图纸了
	    */
		//xls中所有图号
		List<String> numberList = new ArrayList<>();

		List<String> fileCodeNameList = new ArrayList<>();
		List<String> bomFileList = new ArrayList<>();

		// 返回的错误信息
		List<String> checkBomList = new ArrayList<>();

		for (int i = 0; i < files.length; i++) {
			MultipartFile indexFile = files[i];
			if (!indexFile.isEmpty()) {
				String fileName = indexFile.getOriginalFilename();
				if (checkExcel(fileName)) {//是否excel文件
					//step1: 获取MH的图号
					List<String> indexFileCode = machUtils.readExcelCode(indexFile);
					numberList.addAll(indexFileCode);
					bomFileList.add(fileName.trim().substring(0, 13));
				} else {
					// step2:先收集图纸文件中，包含的MH的文件
					String fileCodeName = indexFile.getOriginalFilename().trim().substring(0, 13);
					if(fileCodeName.contains("MH")) {
						fileCodeNameList.add(fileCodeName);
					}
				}
			}
		}
		List<String> queryList = numberList.stream().distinct().collect(Collectors.toList());
		List<String> tempList = new ArrayList<>();
		tempList.addAll(queryList);
		//step3: 判断图纸是否归档
		queryList.forEach(number -> {
			DrawingNumberApplicationDetail detail = drawingNumberApplicationDetailService.getOne(new QueryWrapper<DrawingNumberApplicationDetail>()
				.eq("status", DrawingNumberApplicationDetail.STATUS_ARCHIVED).eq("number", number));
			if(null != detail){
				tempList.remove(number);
			}
		});
		queryList = tempList;
		//对比queryList中的图号
		for (int i = 0; i < queryList.size(); i++) {
			if (!bomFileList.contains(queryList.get(i).trim())) {
				checkBomList.add("代号为" + queryList.get(i) + "的设备缺少相应的BOM信息");
			}
			if (!fileCodeNameList.contains(queryList.get(i).trim())){
				checkBomList.add("代号为" + queryList.get(i) + "的设备缺少相应的图纸文件");
			}
			continue;
		}

		return checkBomList;
	}

	/**
	 * 检验上传的文件图号是否存在未申请。
	 * @param file
	 * @param codeErrorList
	 */
	@Override
	public void applyNumberCheck(MultipartFile[] file, List<String> codeErrorList){
		if (file.length > 0) {
			// step1：检验excel中代号是否申请过
			for (int i = 0; i < file.length; i++) {
				MultipartFile indexFile = file[i];
				String fileName = indexFile.getOriginalFilename();
				if (checkExcel(fileName)) {
					List<String> checkResult = machUtils.verifyExcel(indexFile);
					if (checkResult.size() > 0) {
						codeErrorList.addAll(checkResult);
						return;
					}
				}
			}
			//step2:检验bom信息
			List<String> checkBomResult = verifyBom(file);
			if (checkBomResult.size() > 0) {
				codeErrorList.addAll(checkBomResult);
			}
			System.out.println("codeErrorLit---->" + codeErrorList);
		}
	}
}
